home *** CD-ROM | disk | FTP | other *** search
/ CD Ware Multimedia 1994 November / Cd Ware (Nro. 2) - Epimundo.iso / DOS / PG / MNG132.ZIP / ASMLEX.L next >
Encoding:
Lex Description  |  1994-04-01  |  7.0 KB  |  230 lines

  1. %{
  2. {*  Assembler parsing for Mangler, see MANGLER.L
  3.     Copyright (C) 1993  Berend de Boer
  4.  
  5.     This program is free software for noncommercial users; you can
  6.     redistribute it and/or modify it under the terms of the license,
  7.     stated in de accompanying file LICENSE.TXT.
  8.  
  9.     This program is distributed in the hope that it will be useful,
  10.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12.     license for more details.
  13.  
  14.     See the accompanying READ.ME file for information on contacting the
  15.     author.
  16.  
  17.  
  18. $Author: Berend_de_Boer $
  19. $Date: 93/04/29 07:52:25 $
  20. $Revision: 1.2 $
  21.  
  22. Last changes:
  23. 93-04-19  Fixed the & identifier override bug
  24. *}
  25.  
  26. procedure ParseAsm;
  27.  
  28. %}
  29.  
  30. NQUOTE    [^']
  31. DQUOTE    [^'}]
  32.  
  33. %%
  34.  
  35. %{
  36.   function is_keyword(const id : string) : Boolean;
  37.   {**}
  38.   const
  39.     id_len = 6;
  40.   type
  41.     Ident = string[id_len];
  42.   const
  43.     (* table of assembler keywords: *)
  44.     no_of_keywords = 192;
  45.     keyword : array [1..no_of_keywords] of Ident = (
  46.       'AAA', 'AAD', 'AAM', 'AAS', 'ADC', 'ADD', 'AH', 'AL', 'AND', 'AND',
  47.       'AX', 'BH', 'BL', 'BOUND', 'BP', 'BX', 'BYTE', 'CALL', 'CBW', 'CH',
  48.       'CL', 'CLC', 'CLD', 'CLI', 'CMC', 'CMP', 'CMPS', 'CMPSB', 'CMPSD',
  49.       'CMPSW', 'CS', 'CX', 'DAA', 'DAS', 'DEC', 'DH', 'DI', 'DIV', 'DL', 'DS',
  50.       'DWORD', 'DX', 'ENTER', 'ES', 'FAR', 'HIGH', 'HLT', 'IDIV', 'IMUL',
  51.       'IN', 'INC', 'INS', 'INSB', 'INSD', 'INSW', 'INT', 'INTO', 'IRET', 'JA',
  52.       'JAE', 'JB', 'JBE', 'JC', 'JCXZ', 'JE', 'JG', 'JGE', 'JL', 'JLE', 'JMP',
  53.       'JNA', 'JNAE', 'JNB', 'JNBE', 'JNC', 'JNE', 'JNG', 'JNGE', 'JNL',
  54.       'JNLE', 'JNO', 'JNP', 'JNS', 'JNZ', 'JO', 'JP', 'JPE', 'JPO', 'JS',
  55.       'JZ', 'JZ', 'LAHF', 'LAR', 'LDS', 'LEA', 'LEAVE', 'LES', 'LGDT', 'LIDT',
  56.       'LLDT', 'LMSW', 'LOCK', 'LODS', 'LODSB', 'LODSW', 'LOOP', 'LOOPE',
  57.       'LOOPNE', 'LOOPNZ', 'LOOPZ', 'LOW', 'LSL', 'LTR', 'MOD', 'MOV', 'MOVS',
  58.       'MOVSB', 'MOVSW', 'MUL', 'NEAR', 'NEG', 'NOP', 'NOT', 'NOT', 'OFFSET',
  59.       'OR', 'OR', 'OUT', 'OUTS', 'OUTSB', 'OUTSW', 'POP', 'POPA', 'POPF',
  60.       'PTR', 'PUSH', 'PUSHA', 'PUSHF', 'QWORD', 'RCL', 'RCR', 'REP', 'REPE',
  61.       'REPNE', 'REPNZ', 'REPZ', 'RET', 'ROL', 'ROR', 'SAHF', 'SAL', 'SAR',
  62.       'SBB', 'SCAS', 'SCASB', 'SCASW', 'SEG', 'SEGDS', 'SEGES', 'SEGSS', 'SGDT', 'SHL', 'SHL', 'SHR',
  63.       'SHR', 'SI', 'SIDT', 'SLDT', 'SMSW', 'SP', 'SS', 'ST', 'STC', 'STD',
  64.       'STI', 'STOS', 'STOSB', 'STOSW', 'STR', 'SUB', 'TBYTE', 'TEST', 'TYPE',
  65.       'VERR', 'VERW', 'WAIT', 'WORD', 'XCHG', 'XLAT', 'XLATB', 'XOR', 'XOR');
  66.   var m, n, k : integer;
  67.   begin
  68.     m := 1; n := no_of_keywords;
  69.     while m<=n do  begin
  70.       k := m+(n-m) div 2;
  71.       if id=keyword[k]
  72.        then  begin
  73.          is_keyword := true;
  74.          Exit;
  75.        end
  76.        else  if id>keyword[k]
  77.               then  m := k+1
  78.               else  n := k-1
  79.     end;  { of while }
  80.     is_keyword := false
  81.   end;
  82.  
  83. var
  84.   Stop : Boolean;
  85. %}
  86.  
  87.  
  88.  
  89.  
  90. [A-Za-z]([a-zA-Z])*       begin
  91.                             yytext := UpStr(yytext);
  92.                             if is_keyword(yytext)
  93.                              then  return(KEYWORD)
  94.                              else  begin
  95.                                if yytext = 'END'
  96.                                 then  return(_END)
  97.                                 else  return(IDENTIFIER);
  98.                              end;
  99.                           end;
  100.  
  101. [a-zA-Z_]([a-zA-Z0-9_])*  begin
  102.                             yytext := UpStr(yytext);
  103.                             return(IDENTIFIER);
  104.                           end;
  105.  
  106. "&"                       return(AMPERSAND);
  107.  
  108. [@]+([a-zA-Z0-9_])+       return(_LABEL);
  109.  
  110. ";"              return(SEMICOLON);
  111. "."              return(DOT);
  112.  
  113. '({NQUOTE}|'')*'          return(CHARACTER_STRING);
  114.  
  115. [0-9]([0-9-a-fA-F])*[hH]  |
  116. [$]([0-9a-fA-F])+         |
  117. [0-9]+                    return(NUMBER);
  118.  
  119. "{$"({DQUOTE})*"}"        return(DIRECTIVE);
  120.  
  121. "(*"                      begin
  122.                             Stop := FALSE;
  123.                             repeat
  124.                               if (get_char = '*') and (get_char = ')') then
  125.                                 Stop := TRUE;
  126.                             until Stop;
  127.                           end;
  128.  
  129. "{"                       begin
  130.                 repeat
  131.                             until get_char = '}';
  132.                           end;
  133.  
  134. [ \t\f]              ;
  135.  
  136. \n                        begin
  137.                             if Random(50) = 25 then
  138.                               WriteProgress;
  139.                             return(NEWLINE);
  140.                           end;
  141.  
  142. .                         return(OTHER);
  143.  
  144. %%
  145. (**)
  146.  
  147.   function GiveEncodingFor(s : string) : string;
  148.   {* DO NOT MAKE s a const string!!! *}
  149.   { PRE -
  150.     POST - contents of yytext is destroyed
  151.   }
  152.   var
  153.     p : PScopeCol;
  154.     e : string;
  155.     Index : integer;
  156.   begin
  157.     if yylex = DOT
  158.      then  begin
  159.      {* a dot was used to select a different scope *}
  160.        p := GetScope(s, Index);
  161.        if p = nil
  162.         then  begin     {* an unknown scope was selected *}
  163.           e := s + '.';
  164.           while (yylex = IDENTIFIER) do  begin
  165.             e := e + yytext;
  166.             if yylex = DOT
  167.              then  e := e + '.'
  168.              else  Break;
  169.           end;
  170.           yyless(0);
  171.         end
  172.         else  begin
  173.           PushScope(CurrentScope);
  174.           CurrentScope := p^.AtScope(Index);
  175.           e := p^.AtHashedName(Index) + '.';
  176.           while (yylex = IDENTIFIER) do  begin
  177.             if CurrentScope = nil
  178.              then  e := e + yytext
  179.              else  begin
  180.                CurrentScope^.Search(@yytext, Index);
  181.                e := e + CurrentScope^.AtHashedName(Index);
  182.              end;
  183.             if yylex = DOT
  184.              then  begin
  185.                if CurrentScope <> nil then
  186.                  CurrentScope := CurrentScope^.AtScope(Index);
  187.                e := e + '.';
  188.              end
  189.              else  Break;
  190.           end;  { of while }
  191.           yyless(0);
  192.           CurrentScope := PopScope;
  193.         end;
  194.        GiveEncodingFor := e;
  195.      end
  196.      else  begin
  197.        yyless(0);
  198.        p := GetScope(s, Index);
  199.        if p = nil
  200.         then  GiveEncodingFor := s
  201.         else  GiveEncodingFor := p^.AtHashedName(Index)
  202.      end;
  203.   end;
  204.  
  205. begin
  206.   write(yyoutput, yytext, ' ');
  207.   while yylex <> _END do  begin
  208.     case yyretval of
  209.       IDENTIFIER : write(yyoutput, GiveEncodingFor(yytext));
  210.       NEWLINE : writeln(yyoutput, '{}');
  211.       AMPERSAND : begin
  212.           write(yyoutput, yytext);
  213.           yylex;
  214.           write(yyoutput, GiveEncodingFor(yytext));
  215.         end;
  216.     else  write(yyoutput, yytext, ' ');
  217.     end; { of case }
  218.   end; { of while }
  219.   writeln(yyoutput);
  220.   write(yyoutput, yytext);
  221.   if AssemblerSection then  begin
  222.     Section := PopSection;
  223.     CurrentScope := PopScope;
  224.     if ObjectImpl then  begin
  225.       CurrentScope := PopScope;
  226.       ObjectImpl := FALSE;
  227.     end;
  228.     AssemblerSection := FALSE;
  229.   end;
  230. end;